package com.lingo.ffmpegdemo.screen.demo;

import com.spicdt.iot.api.entity.FileUploadFile;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.ChannelInboundHandlerAdapter;
import lombok.extern.slf4j.Slf4j;

import java.io.RandomAccessFile;
import java.net.InetSocketAddress;
@Slf4j
public class ServerHandler extends ChannelInboundHandlerAdapter {
    private int total; //总包数量
    private int row;//剩余包数
    private int byteRead; //读取结束位置
    private volatile int start = 0; //开始位置
    private volatile int lastLength = 0;//文件读取长度
    public RandomAccessFile randomAccessFile;
    private FileUploadFile fileUploadFile;

    public ServerHandler(FileUploadFile fileUploadFile) {
        if (fileUploadFile.getFile().exists()){
            if (!fileUploadFile.getFile().isFile()){
                log.warn("this is not a file");
                return;
            }
        }
        this.fileUploadFile = fileUploadFile;
    }

    /*
     * 客户端连接会触发该方法
     * */
    @Override
    public void channelActive(ChannelHandlerContext ctx) {
        InetSocketAddress remoteAddress = (InetSocketAddress) ctx.channel().remoteAddress();
        String ip = remoteAddress.getAddress().getHostAddress();
        log.info("有客户端连接，ip地址为：{}",ip);
        log.info("开始发送FileUploadFile 对象");
        try{
            randomAccessFile = new RandomAccessFile(fileUploadFile.getFile(),"r");//文件只读，不存在不创建，抛出异常
            randomAccessFile.seek(fileUploadFile.getStartPos());//开始位置初始为0
            lastLength =1024;
            if(((randomAccessFile.length())%lastLength)!=0){
                total = (int) (randomAccessFile.length()/lastLength+1);
            }else {
                total = (int) (randomAccessFile.length()/lastLength);
            }
            row = total;
            byte[] body = new byte[lastLength];//创建一个字节长度为1024数组
            if ((byteRead = randomAccessFile.read(body))!=-1){
                fileUploadFile.setEndPos(byteRead);//存入结束位置
                fileUploadFile.setBody(body);//存入文件字节
                ctx.writeAndFlush(fileUploadFile);//发送对象
            }
            row--;
            log.info("第一段文件读取完毕！");
            log.info("文件总长度：[{}],剩余长度:[{}],发送长度:[{}]",randomAccessFile.length(),randomAccessFile.length()-byteRead,byteRead);
            log.info("总包数:[{}]，剩余包数:[{}]",total,row);

        }catch (Exception e){
            e.printStackTrace();
        }
    }


    /*
     * 接收信息
     * */
    @Override
    public void channelRead(ChannelHandlerContext ctx, Object msg) throws Exception{
        if (msg instanceof Integer){
            start  = (int) msg;
            if (start!=-1){
                randomAccessFile = new RandomAccessFile(fileUploadFile.getFile(),"r");
                randomAccessFile.seek(start); //定位文件位置
                int  a = (int) (randomAccessFile.length()-start);
                if (a < lastLength){ //剩余长度小于1024一次发完
                    lastLength = a;
                }
                byte[] body = new byte[lastLength];
                if ((byteRead = randomAccessFile.read(body))!=-1 && a>0){
                    fileUploadFile.setBody(body);
                    fileUploadFile.setEndPos(byteRead);
                    ctx.writeAndFlush(fileUploadFile);
                    row--;
                    log.info("文件总长度：[{}],剩余长度:[{}],发送长度:[{}]",randomAccessFile.length(),a,byteRead);
                    log.info("总包数:[{}]，剩余包数:[{}]",total,row);
                }else {
                    log.info("文件已全部发送完毕,即将关闭通道");
                    randomAccessFile.close();
                    ctx.flush();
                    ctx.close();
                }
            }
        }
    }

    /*
     * 连接异常触发
     * */
    @Override
    public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
        cause.printStackTrace();
        ctx.close();
    }
}

